/*
 *
 *  Copyright (C) THL A29 Limited, a Tencent company. All rights reserved.
 *  SPDX-License-Identifier: Apache-2.0
 *
 */
import {
  Button,
  Form,
  Input,
  Justify,
  Layout,
  Modal,
  SearchBox,
  Select,
  Table,
  TableColumn,
  Text,
} from 'tea-component';
import React, { Ref, useCallback, useContext, useEffect, useImperativeHandle, useMemo, useRef, useState } from 'react';
import {
  ChainContractMethodsDecoded,
  ContractInstallRequest,
  ContractManage,
  ContractManageListRequest,
  ContractStatusEnum,
  ContractUpgradeRequest,
  InvokeRecordRequest,
} from '../../common/apis/chains/interface';
import { formatDate } from '../../utils/date';
import {
  useContractDelete,
  useContractInstall,
  useContractOperation,
  useContractUpgrade,
  useFetchChainContractDetail,
  useFetchContractManageList,
  useFetchContractRuntimeTypeList,
} from '../../common/apis/chains/hooks';
import { ChainDetailContext } from './chain-detail';
import { autotip, pageable } from 'tea-component/es/table/addons';
import { PAGE_SIZE_OPTIONS, safeParseArrayStr, splitUrl } from '../../utils/common';
import { ValueOf } from '../../common/interface';
import { Controller, useForm, useWatch } from 'react-hook-form';
import formUtils, { Validator } from '../../utils/form-utils';
import { TextTheme, UploadFile } from 'src/common/components/upload-file';
import { TextArea } from 'tea-component/es/input';
import { ChainParamsInput } from './chain-invoke-contracts';
import GlossaryGuide from 'src/common/components/glossary-guide';
import { useHistory, useRouteMatch } from 'react-router-dom';
import { ContractRuntimeTypeEnum } from './contract/contract-detail';

const { Content } = Layout;

type OnOperate = (contract: ContractManage, operate: ContractOperateType) => void;

const VOTE_STATUS_MAP: {
  [index: number]: {
    theme: TextTheme;
    label: string;
  };
} = {
  0: {
    theme: 'warning',
    label: '投票中',
  },
  1: {
    theme: 'success',
    label: '正常',
  },
};

const defaultColumns = (onOperate: OnOperate): TableColumn<ContractManage>[] =>
  [
    {
      key: 'ContractName',
      header: '合约名称',
    },
    {
      key: 'Version',
      header: '当前版本',
    },
    splitUrl(location.search).get('chainMode') === 'public'
      ? {
          key: 'null',
          header: 'null',
        }
      : {
          key: 'OrgName',
          header: '所属组织',
        },
    {
      key: 'UserName',
      header: '创建者',
    },
    {
      key: 'CreateTime',
      header: '更新时间',
      render: (record: { CreateTime: number | undefined }) => formatDate(record.CreateTime),
    },
    {
      key: 'VoteStatus',
      header: '投票状态',
      // eslint-disable-next-line react/display-name
      render: (record: { VoteStatus: number }) => {
        const item = VOTE_STATUS_MAP[record.VoteStatus];
        return <Text theme={item.theme}>{item.label}</Text>;
      },
    },
    {
      key: 'Status',
      header: '链上状态',
      // eslint-disable-next-line react/display-name
      render: (record: { Status: number }) => {
        const item = CONTRACT_STATUS_MAP[record.Status];
        return item && <Text theme={item.theme}>{item.label}</Text>;
      },
    },
    {
      key: 'Id',
      header: '操作',
      // eslint-disable-next-line react/display-name
      render: (record: ContractManage) => <ContractOptions contract={record} onOperate={onOperate} />,
    },
  ].filter((item) => item.key !== 'null');

const CONTRACT_STATUS_MAP: {
  [index: number]: {
    theme: TextTheme;
    label: string;
  };
} = {
  0: {
    theme: 'success',
    label: '待上链',
  },
  1: {
    theme: 'success',
    label: '升级合约已存储',
  },
  2: {
    theme: 'danger',
    label: '部署失败',
  },
  3: {
    theme: 'success',
    label: '正常',
  },
  4: {
    theme: 'danger',
    label: '合约升级部署失败',
  },
  5: {
    theme: 'success',
    label: '正常',
  },
  6: {
    theme: 'warning',
    label: '合约冻结失败',
  },
  7: {
    theme: 'success',
    label: '已冻结',
  },
  8: {
    theme: 'danger',
    label: '合约解冻失败',
  },
  9: {
    theme: 'success',
    label: '正常',
  },
  10: {
    theme: 'danger',
    label: '合约注销失败',
  },
  11: {
    theme: 'success',
    label: '已注销',
  },
};

export type ContractOperateType = {
  value: string;
  caption: string;
  placeholder: string;
  description: string;
};

export const OPERATE_TYPE: {
  [key: string]: ContractOperateType;
} = {
  freeze: {
    value: 'freeze',
    caption: '冻结合约',
    placeholder: '请输入冻结合约理由(选填)',
    description: '冻结合约需经过其它组织投票同意，请输入冻结理由。',
  },
  revoke: {
    value: 'revoke',
    caption: '废止合约',
    placeholder: '请输入废止合约理由(选填)',
    description: '废止合约需经过其它组织投票同意，请输入废止理由。',
  },
  unfreeze: {
    value: 'unfreeze',
    caption: '解冻合约',
    placeholder: '请输入解冻合约理由(选填)',
    description: '解冻合约需经过其它组织投票同意，请输入解冻理由。',
  },
  // 升级复用的部署安装逻辑/弹窗
  upgrade: {
    value: '',
    caption: '',
    placeholder: '',
    description: '',
  },
  delete: {
    value: '',
    caption: '',
    placeholder: '',
    description: '',
  },
  reinstall: {
    value: '',
    caption: '',
    placeholder: '',
    description: '',
  },
};

function renderContractDetailBtn(go: (p: string) => void, url: string, contract: ContractManage) {
  if (contract.VoteStatus === 0) {
    return null;
  }
  const chainMode = splitUrl(location.search).get('chainMode');
  return (
    <Button
      type={'link'}
      onClick={() => {
        go(`${url}/details/${contract.Id}?chainMode=${chainMode}`);
      }}
    >
      {contract.Status === ContractStatusEnum.ContractRevokeOK.value ? '查看' : '编辑'}
    </Button>
  );
}
// 合约列表操作列
function ContractOptions({ contract, onOperate }: { contract: ContractManage; onOperate: OnOperate }) {
  const handleFreezeClick = useCallback(() => onOperate(contract, OPERATE_TYPE.freeze), [contract]);
  const handleRevokeClick = useCallback(() => onOperate(contract, OPERATE_TYPE.revoke), [contract]);
  const handleUnfreezeClick = useCallback(() => onOperate(contract, OPERATE_TYPE.unfreeze), [contract]);
  const handleUpgradeClick = useCallback(() => onOperate(contract, OPERATE_TYPE.upgrade), [contract]);
  const handleDeleteClick = useCallback(() => onOperate(contract, OPERATE_TYPE.delete), [contract]);
  const handleReInstallClick = useCallback(() => onOperate(contract, OPERATE_TYPE.reinstall), [contract]);
  const { url } = useRouteMatch();
  const go = useHistory();
  return (
    <>
      {[
        ContractStatusEnum.ContractUpgradeStored.value,
        ContractStatusEnum.ContractInitOk.value,
        ContractStatusEnum.ContractUpgradeFailure.value,
        ContractStatusEnum.ContractUpgradeOK.value,
        ContractStatusEnum.ContractFreezeFailure.value,
        ContractStatusEnum.ContractUnfreezeOK.value,
        ContractStatusEnum.ContractRevokeFailure.value,
      ].includes(contract.Status) && (
        <Button type={'link'} onClick={handleFreezeClick}>
          冻结
        </Button>
      )}
      {[
        ContractStatusEnum.ContractUpgradeStored.value,
        ContractStatusEnum.ContractInitOk.value,
        ContractStatusEnum.ContractUpgradeFailure.value,
        ContractStatusEnum.ContractUpgradeOK.value,
        ContractStatusEnum.ContractFreezeFailure.value,
        ContractStatusEnum.ContractFreezeOK.value,
        ContractStatusEnum.ContractUnfreezeFailure.value,
        ContractStatusEnum.ContractUnfreezeOK.value,
        ContractStatusEnum.ContractRevokeFailure.value,
      ].includes(contract.Status) && (
        <Button type={'link'} onClick={handleRevokeClick}>
          注销
        </Button>
      )}
      {[ContractStatusEnum.ContractFreezeOK.value, ContractStatusEnum.ContractUnfreezeFailure.value].includes(
        contract.Status,
      ) && (
        <Button type={'link'} onClick={handleUnfreezeClick}>
          解冻
        </Button>
      )}
      {[
        ContractStatusEnum.ContractInitOk.value,
        ContractStatusEnum.ContractUpgradeOK.value,
        ContractStatusEnum.ContractFreezeFailure.value,
        ContractStatusEnum.ContractUnfreezeOK.value,
        ContractStatusEnum.ContractRevokeFailure.value,
        ContractStatusEnum.ContractUpgradeFailure.value,
      ].includes(contract.Status) && (
        <Button type={'link'} onClick={handleUpgradeClick}>
          升级
        </Button>
      )}
      {renderContractDetailBtn(go.push, url, contract)}
      {ContractStatusEnum.ContractInitFailure.value === contract.Status && (
        <>
          <Button type={'link'} onClick={handleReInstallClick}>
            重新部署
          </Button>
          <Button type={'link'} onClick={handleDeleteClick}>
            删除
          </Button>
        </>
      )}
    </>
  );
}
// 合约列表页面
export default function ChainContracts() {
  const { chainId } = useContext(ChainDetailContext);
  const [queryParams, setQueryParams] = useState<ContractManageListRequest>({
    ChainId: chainId as string,
    PageSize: 20,
    PageNum: 0,
  });
  const {
    data: { list: contractList, totalCount },
    run: fetchContractList,
  } = useFetchContractManageList();
  const { run: fetchContractDelete } = useContractDelete();

  useEffect(() => {
    fetchContractList(queryParams);
  }, [queryParams]);

  const getList = useCallback(() => {
    fetchContractList(queryParams);
  }, [queryParams]);

  const onSearch = useCallback(
    (value) => {
      setQueryParams({
        ...queryParams,
        ContractName: value ? value : undefined,
      });
    },
    [queryParams],
  );

  const [selectedContract, setSelectedContract] = useState<ContractManage | null>(null);
  const [freezeModalVisible, setFreezeModalVisible] = useState(false);
  const [revokeModalVisible, setRevokeModalVisible] = useState(false);
  const [unfreezeModalVisible, setUnfreezeModalVisible] = useState(false);
  const contractInstallRef = useRef<any>();

  const handleInstallClick = useCallback(() => {
    contractInstallRef.current.showModal();
  }, [contractInstallRef]);

  const onOperate = useCallback(
    async (contract: ContractManage, operate: ValueOf<typeof OPERATE_TYPE>) => {
      setSelectedContract(contract);

      if (operate === OPERATE_TYPE.freeze) {
        setFreezeModalVisible(true);
        return;
      }
      if (operate === OPERATE_TYPE.revoke) {
        setRevokeModalVisible(true);
        return;
      }
      if (operate === OPERATE_TYPE.unfreeze) {
        setUnfreezeModalVisible(true);
        return;
      }
      if (operate === OPERATE_TYPE.upgrade) {
        contractInstallRef.current.showModal(contract, true);
        return;
      }
      if (operate === OPERATE_TYPE.delete) {
        const yes = await Modal.confirm({
          message: '删除确认',
          description: '该合约并未完成上链，请确定是否删除该合约，删除后可重新部署',
          okText: '删除',
          cancelText: '取消',
        });
        if (yes) {
          fetchContractDelete({
            ChainId: chainId as string,
            ContractName: contract.ContractName,
          }).then(() => {
            getList();
          });
        }
        return;
      }
      if (operate === OPERATE_TYPE.reinstall) {
        contractInstallRef.current.showModal(contract);
        return;
      }
    },
    [contractInstallRef, getList],
  );

  const columns = useMemo(() => defaultColumns(onOperate), []);

  return (
    <Content>
      <Content.Header title="区块链管理/合约管理" />
      <Content.Body full>
        <Justify
          left={
            <Button type={'primary'} onClick={handleInstallClick}>
              部署合约
            </Button>
          }
          right={
            <SearchBox placeholder="请输入合约名称搜索" size="l" onSearch={onSearch} onClear={() => onSearch(null)} />
          }
        />
        <Table
          columns={columns}
          records={contractList}
          className={'tea-mt-5n'}
          addons={[
            pageable({
              pageSizeOptions: PAGE_SIZE_OPTIONS,
              pageSize: queryParams.PageSize,
              pageIndex: queryParams.PageNum + 1,
              recordCount: totalCount,
              onPagingChange: ({ pageIndex, pageSize }) => {
                setQueryParams({
                  ...queryParams,
                  PageNum: (pageIndex as number) - 1,
                  PageSize: pageSize as number,
                });
              },
            }),
            autotip({
              emptyText: '暂无数据',
            }),
          ]}
        />
        {selectedContract && (
          <>
            <ContractOperationModal
              type={OPERATE_TYPE.freeze}
              contract={selectedContract as ContractManage}
              visible={freezeModalVisible}
              onClose={() => {
                setFreezeModalVisible(false);
              }}
              onSubmit={() => {
                setFreezeModalVisible(false);
                fetchContractList(queryParams);
              }}
            />
            <ContractOperationModal
              type={OPERATE_TYPE.revoke}
              contract={selectedContract as ContractManage}
              visible={revokeModalVisible}
              onClose={() => {
                setRevokeModalVisible(false);
                fetchContractList(queryParams);
              }}
              onSubmit={() => {
                setRevokeModalVisible(false);
                fetchContractList(queryParams);
              }}
            />
            <ContractOperationModal
              type={OPERATE_TYPE.unfreeze}
              contract={selectedContract as ContractManage}
              visible={unfreezeModalVisible}
              onClose={() => {
                setUnfreezeModalVisible(false);
              }}
              onSubmit={() => {
                setUnfreezeModalVisible(false);
                fetchContractList(queryParams);
              }}
            />
          </>
        )}
        <ContractInstallModal
          ref={contractInstallRef}
          onSubmit={() => {
            fetchContractList(queryParams);
          }}
        />
      </Content.Body>
    </Content>
  );
}
// 合约冻结/撤销/解冻
function ContractOperationModal(props: {
  contract: ContractManage;
  visible: boolean;
  type: ContractOperateType;
  onClose?: () => void;
  onSubmit?: () => void;
}) {
  const { chainId } = useContext(ChainDetailContext);
  const [visible, setVisible] = useState(props.visible);
  const [isSubmitting, setIsSubmitting] = useState(false);
  const onClose = useCallback(() => {
    setVisible(false);
    props.onClose?.();
  }, [props]);
  const { run: doOperation } = useContractOperation();

  const {
    control,
    formState: { isValidating, isSubmitted, isValid },
    getValues,
  } = useForm({ mode: 'onBlur' });

  const handleSubmit = useCallback(async () => {
    try {
      setIsSubmitting(true);
      await doOperation(
        {
          ChainId: chainId as string,
          ContractName: props.contract.ContractName,
          Reason: getValues().Reason,
        },
        props.type,
      );
      setIsSubmitting(false);
      props.onSubmit?.();
    } catch {
      setVisible(false);
    }
  }, [props.contract]);

  useEffect(() => {
    setVisible(props.visible);
  }, [props.visible]);

  return (
    <Modal visible={visible} caption={props.type.caption} onClose={onClose}>
      <Modal.Body>
        {props.type.description}
        <Form className={'tea-mt-2n'}>
          <Controller
            control={control}
            name="Reason"
            rules={{
              validate: Validator.validateReason,
            }}
            render={({ field, fieldState }) => (
              <Form.Item
                status={formUtils.getStatus({
                  fieldState,
                  isValidating,
                  isSubmitted,
                })}
                label={'理由'}
                message={fieldState.error?.message}
              >
                <TextArea showCount size={'full'} placeholder={props.type.placeholder} {...field} />
              </Form.Item>
            )}
          />
        </Form>
      </Modal.Body>
      <Modal.Footer>
        <Button type="primary" disabled={!isValid} onClick={handleSubmit} loading={isSubmitting}>
          确定
        </Button>
        <Button type="weak" onClick={onClose}>
          取消
        </Button>
      </Modal.Footer>
    </Modal>
  );
}

const ContractInstallModal = React.forwardRef(ContractInstallModalContainer);

/**
 * 合约安装/更新
 */
function ContractInstallModalContainer(
  props: {
    onClose?: () => void;
    onSubmit?: () => void;
  },
  ref: Ref<any>,
) {
  const {
    control,
    reset,
    formState: { isValidating, isSubmitted, isValid },
    getValues,
    setValue,
    trigger,
  } = useForm({ mode: 'onBlur' });

  const { chainId } = useContext(ChainDetailContext);
  const [visible, setVisible] = useState(false);
  const [contract, setContract] = useState<ContractManage | null>();
  const [caption, setCaption] = useState<string>('');
  const paramsInputParametersRef = useRef<any>();
  const paramsInputMethodsRef = useRef<any>();
  const [isSubmitting, setIsSubmitting] = useState(false);

  const [isUpgrade, setIsUpgrade] = useState(false);
  const runtimeTypeWatch = useWatch({ name: 'RuntimeType', control });
  const onClose = useCallback(() => {
    setVisible(false);
    reset(contract ?? {});
  }, [contract]);

  const uploadFileRef = useRef<any>(null);
  const uploadAbiFileRef = useRef<any>(null);
  const { runtimeTypeList, run: fetchRuntimeTypeList } = useFetchContractRuntimeTypeList();
  const { fetch: fetchContractDetail, detail: contractDetail } = useFetchChainContractDetail();
  const { run: contractInstall } = useContractInstall();
  const { run: contractUpgrade } = useContractUpgrade();

  const onSubmit = useCallback(async () => {
    setIsSubmitting(true);
    if (isUpgrade) {
      try {
        await contractUpgrade({
          ...(getValues() as ContractUpgradeRequest),
          RuntimeType: +getValues('RuntimeType'),
          ChainId: chainId as string,
        });
      } catch {}
    } else {
      try {
        await contractInstall({
          ...(getValues() as ContractInstallRequest),
          RuntimeType: +getValues('RuntimeType'),
          ChainId: chainId as string,
        });
      } catch {}
    }
    setIsSubmitting(false);
    setVisible(false);
    props.onSubmit?.();
  }, [isUpgrade]);

  useEffect(() => {
    fetchRuntimeTypeList();
  }, []);

  useImperativeHandle(ref, () => ({
    showModal: (contract: ContractManage | null = null, isUpgrade?: boolean) => {
      reset(contract ?? {});
      setContract(contract);
      setIsUpgrade(Boolean(isUpgrade));
      setVisible(true);
    },
  }));
  useEffect(() => {
    let captionText = '';
    if (isUpgrade) {
      captionText = '升级合约';
    } else {
      if (contract) {
        captionText = '重新部署';
        fetchContractDetail({ Id: contract.Id });
      } else {
        captionText = '部署合约';
      }
    }
    setCaption(captionText);
  }, [contract, isUpgrade]);
  useEffect(() => {
    if (contractDetail && !isUpgrade) {
      // console.log(safeParseArrayStr(contractDetail.Parameters))
      // console.log(safeParseArrayStr(contractDetail.Methods))
      setValue('ContractName', contractDetail.ContractName);
      setValue('ContractVersion', contractDetail.ContractVersion);
      setValue('RuntimeType', contractDetail.RuntimeType);
      setValue('Reason', contractDetail.Reason);
      paramsInputParametersRef.current?.updateParams(safeParseArrayStr(contractDetail.Parameters));
      paramsInputMethodsRef.current?.updateParams(safeParseArrayStr(contractDetail.Methods));
    } else {
      setValue('ContractName', contract?.ContractName || '');
      setValue('ContractVersion', '');
      setValue('RuntimeType', '');
      setValue('Reason', '');
      paramsInputParametersRef.current?.updateParams([]);
      paramsInputMethodsRef.current?.updateParams([]);
    }
  }, [isUpgrade, contract, contractDetail]);

  useEffect(() => {
    trigger();
  }, [runtimeTypeWatch]);

  return (
    <>
      <Modal size={600} visible={visible} caption={caption} onClose={onClose}>
        <Modal.Body>
          <Form>
            <Controller
              control={control}
              rules={{
                validate: Validator.validateContractName,
              }}
              defaultValue={contract?.ContractName}
              name="ContractName"
              render={({ field, fieldState }) => (
                <Form.Item
                  label={<GlossaryGuide title={'合约名称'} />}
                  required
                  status={formUtils.getStatus({
                    fieldState,
                    isValidating,
                    isSubmitted,
                  })}
                  message={fieldState.error?.message}
                >
                  {contract?.ContractName ? (
                    <Form.Text>{contract?.ContractName}</Form.Text>
                  ) : (
                    <Input autoComplete="off" {...field} size={'full'} />
                  )}
                </Form.Item>
              )}
            />
            {!isUpgrade || (
              <Form.Item label="当前版本号">
                <Form.Text>{contract?.Version}</Form.Text>
              </Form.Item>
            )}
            <Controller
              control={control}
              rules={{
                validate: isUpgrade
                  ? Validator.validateUpgradeContractVersion(contract?.Version)
                  : Validator.validateContractVersion,
              }}
              defaultValue={contract?.Version}
              name="ContractVersion"
              render={({ field, fieldState }) =>
                isUpgrade ? (
                  <Form.Item
                    status={formUtils.getStatus({
                      fieldState,
                      isValidating,
                      isSubmitted,
                    })}
                    required
                    label="升级版本号"
                    message={fieldState.error?.message || '合约版本号供识别与维护使用，必须大于当前版本号。'}
                  >
                    <Input autoComplete="off" placeholder={'请输入升级版本号'} {...field} size={'full'} />
                  </Form.Item>
                ) : (
                  <Form.Item
                    status={formUtils.getStatus({
                      fieldState,
                      isValidating,
                      isSubmitted,
                    })}
                    required
                    label="合约版本"
                    message={fieldState.error?.message}
                  >
                    <Input autoComplete="off" {...field} size={'full'} />
                  </Form.Item>
                )
              }
            />
            <Controller
              control={control}
              defaultValue={contract?.RuntimeType}
              rules={{
                required: '请选择虚拟机类型',
              }}
              name="RuntimeType"
              render={({ field, fieldState }) => (
                <>
                  <Form.Item
                    status={formUtils.getStatus({
                      fieldState,
                      isValidating,
                      isSubmitted,
                    })}
                    required
                    label={<GlossaryGuide title={'虚拟机类型'} />}
                    message={fieldState.error?.message}
                  >
                    <>
                      <Select
                        placeholder={'请选择虚拟机类型'}
                        options={runtimeTypeList?.map((item) => ({
                          text: item.RuntimeTypeName,
                          value: String(item.RuntimeTypeType),
                        }))}
                        {...field}
                        size="full"
                      />
                    </>
                  </Form.Item>
                </>
              )}
            />
            {String(runtimeTypeWatch) === '6' && (
              <div className={'tea-form__item text-size-base'}>
                <div className={'tea-form__label'} />
                <div>
                  目前只有v2.1.0版本及以上的chainmaker支持docker_go，请确保您的链版本在v2.1.0以上，且开启docker-vm，详情可见开源文档。
                </div>
              </div>
            )}
            <Controller
              control={control}
              name="CompileSaveKey"
              rules={{
                validate: (value) => {
                  if (!value && uploadFileRef.current?.status === null) {
                    return '请上传合约文件';
                  }
                  if (!value && uploadFileRef.current?.status === 'error') {
                    return '上传合约文件格式不正确';
                  }
                  return undefined;
                },
              }}
              render={({ field, fieldState }) => (
                <Form.Item
                  className="chain-upload"
                  required
                  status={uploadFileRef.current?.status}
                  label="合约文件"
                  message={fieldState.error?.message}
                >
                  <UploadFile
                    {...field}
                    accept=".wasm,.bin,.7z"
                    ref={uploadFileRef}
                    onSuccess={(key: string | null) => {
                      setValue(field.name, key, {
                        shouldValidate: true,
                      });
                    }}
                  />
                </Form.Item>
              )}
            />
            {runtimeTypeWatch == ContractRuntimeTypeEnum.EVM && (
              <Controller
                control={control}
                name="EvmAbiSaveKey"
                rules={{
                  validate: (value) => {
                    if (!value && uploadAbiFileRef.current?.status === null) {
                      return '请上传合约文件';
                    }
                    if (!value && uploadAbiFileRef.current?.status === 'error') {
                      return '上传合约文件格式不正确';
                    }
                    return undefined;
                  },
                }}
                render={({ field, fieldState }) => (
                  <Form.Item
                    className="chain-upload"
                    status={uploadAbiFileRef.current?.status}
                    label="ABI文件"
                    message={fieldState.error?.message}
                    required
                  >
                    <UploadFile
                      {...field}
                      accept=".abi"
                      ref={uploadAbiFileRef}
                      onSuccess={(key: string | null) => {
                        setValue(field.name, key, {
                          shouldValidate: true,
                        });
                      }}
                    />
                  </Form.Item>
                )}
              />
            )}
            <Controller
              control={control}
              name="Reason"
              rules={{
                validate: Validator.validateReason,
              }}
              render={({ field, fieldState }) => (
                <Form.Item
                  status={formUtils.getStatus({
                    fieldState,
                    isValidating,
                    isSubmitted,
                  })}
                  label={isUpgrade ? '升级理由' : '部署理由'}
                  message={fieldState.error?.message}
                >
                  <TextArea
                    size="full"
                    showCount
                    placeholder={
                      isUpgrade
                        ? '升级合约需其他组织同意，请输入升级理由（选填）'
                        : '部署合约需其他组织同意，请输入部署理由（选填）'
                    }
                    {...field}
                  />
                </Form.Item>
              )}
            />
            <Form.Item label={<GlossaryGuide title={'额外信息(选填)'} />}></Form.Item>
          </Form>
          <div>
            <Controller
              control={control}
              name="Parameters"
              render={({ field }) => (
                <ChainParamsInput
                  ref={paramsInputParametersRef}
                  onChange={(params: InvokeRecordRequest['Parameters']) => setValue(field.name, params)}
                  paramKeys={['Key', 'Value']}
                />
              )}
            />
          </div>
          {runtimeTypeWatch != ContractRuntimeTypeEnum.EVM && (
            <>
              <Form className={'content-mt-2n'}>
                <Form.Item label={<GlossaryGuide title={'合约调用方法(选填)'} />}></Form.Item>
              </Form>
              <div>
                <Controller
                  control={control}
                  name="Methods"
                  render={({ field }) => (
                    <ChainParamsInput
                      ref={paramsInputMethodsRef}
                      onChange={(params: ChainContractMethodsDecoded) => setValue(field.name, params)}
                      paramKeys={['MethodName', 'MethodFunc', 'MethodKey']}
                      placeholders={['Method', 'MethodFunc', 'Param，例 key1，key2，key3']}
                    />
                  )}
                />
              </div>
            </>
          )}
        </Modal.Body>
        <Modal.Footer>
          <Button
            type="primary"
            onClick={onSubmit}
            disabled={!isValid || !Boolean(getValues().CompileSaveKey)}
            loading={isSubmitting}
          >
            确定
          </Button>
          <Button type="weak" onClick={onClose}>
            取消
          </Button>
        </Modal.Footer>
      </Modal>
    </>
  );
}
